package com.cyj.dream.core.interceptor;

import cn.hutool.core.util.StrUtil;
import com.cyj.dream.core.aspect.annotation.ResponseResult;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerInterceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.lang.reflect.Method;

/**
 * @Description: 用于拦截请求，判断 Controller 是否添加了@ResponseResult注解
 * @BelongsProject: DreamChardonnay
 * @BelongsPackage: com.cyj.dream.core.interceptor
 * @Author: ChenYongJia
 * @CreateTime: 2021-09-26 10:52
 * @Email: chen87647213@163.com
 * @Version: 1.0
 */
@Slf4j
@Component
public class ResponseResultInterceptor implements HandlerInterceptor {

    /**
     * 标记名称
     */
    public static final String RESPONSE_RESULT_ANN = "RESPONSE-RESULT-ANN";

    /**
     * preHandle：预处理回调方法，实现处理器的预处理（如登录检查），第三个参数为版响应的处理器；
     * 返回值权：true表示继续流程（如调用下一个拦截器或处理器）；
     * false表示流程中断（如登录检查失败），不会继续调用其他的拦截器或处理器，
     *
     * @param request
     * @param response
     * @param handler
     * @return boolean
     * @date 2021/4/17 9:43
     * @author ChenYongJia
     * @version 1.0
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        log.info("本次请求路径======>{}", request.getRequestURI());
        try {
            if (handler instanceof HandlerMethod) {
                final HandlerMethod handlerMethod = (HandlerMethod) handler;
                final Class<?> clazz = handlerMethod.getBeanType();
                final Method method = handlerMethod.getMethod();
                // 判断是否在类对象上添加了注解
                if (clazz.isAnnotationPresent(ResponseResult.class)) {
                    // 设置此请求返回体，需要包装，往下传递，在ResponseBodyAdvice接口进行判断
                    request.setAttribute(RESPONSE_RESULT_ANN, clazz.getAnnotation(ResponseResult.class));
                } else if (method.isAnnotationPresent(ResponseResult.class)) {
                    request.setAttribute(RESPONSE_RESULT_ANN, method.getAnnotation(ResponseResult.class));
                }
            }

            // 获取请求头中JWT的Token
            /*String tokenHeader = request.getHeader(Constant.tokenHeader);
            log.info("拿到的 tokenHeader 头部信息===>" + tokenHeader);
            if(!StrUtil.isEmpty(tokenHeader)){
                //从请求认证服务获取用户信息
                UserInfoDTO userInfo = BasicInfoSelect.getUserContext();
                UserContext.set(userInfo);
            }*/
            return Boolean.TRUE;
        } catch (Exception e) {
            log.error("拦截器错误======> {}", e);
            return Boolean.FALSE;
        }
    }

    /**
     * 在整个请求结束之后被调用（主要是用于进行资源清理工作）
     * 一定要在请求结束后调用remove清除当前线程的副本变量值，否则会造成内存泄漏
     *
     * @param request
     * @param response
     * @param object
     * @param ex
     * @return void
     * @date 2021/4/17 9:43
     * @author ChenYongJia
     * @version 1.0
     */
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object object, Exception ex)
            throws Exception {
        //UserContext.remove();
    }

}
